home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
GFX Sensations 1
/
Graphic Sensations - Volume 1.iso
/
tools
/
amiga
/
3d_tools
/
shelly14.lha
/
shelly
/
shelly.c
< prev
next >
Wrap
C/C++ Source or Header
|
1994-04-25
|
31KB
|
1,293 lines
/*****************************************************/
/* ShellyV1.4: The ShellShapeGenerator by: */
/* RANDi */
/* (rschultz@informatik.uni-rostock.de) */
/*****************************************************/
#include <math.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <memory.h>
#include "shelly.h"
int countw = 0, counth = 0, countp = 0;
double camx = 0, camy = 500, camz = 500;
/********************************************/
/*cot: */
/********************************************/
double
cot (double in)
{
if (sin (in) == 0)
return (0);
else
return (cos (in) / sin (in));
}
/********************************************/
/*round: */
/********************************************/
double
round (double in)
{
if (in - floor (in) < 0.5)
return (floor (in));
else
return (floor (in) + 1);
}
/********************************************/
/*myfree: */
/********************************************/
int
myfree (struct punkt *anker1)
{
struct punkt *hp, *hpnew;
if (anker1 == NULL)
return (0);
hp = anker1;
hpnew = hp;
do
{
hp = hpnew;
hpnew = (*hp).next;
free (hp);
}
while (hpnew != NULL);
return (0);
}
/********************************************/
/*mycopystr: */
/********************************************/
char *
mycopystr (char *source, char *destination, char endchar)
{
int ende = 1;
char *merk;
merk = destination; /* merk points now on destination */
while (ende)
{
if ((*source == '\0') || (*source == endchar))
{
ende = 0;
}
else
{
*destination = *source;
destination++;
source++;
} /* if */
} /* while */
*destination = '\0';
return (merk);
}
/********************************************/
/*filecopy: */
/********************************************/
void
filecopy (FILE * source, FILE * dest)
{
int a, b;
fseek (source, 0, 0);
do
{
a = fgetc (source);
if (a != EOF)
{
b = fputc (a, dest);
if (b == EOF)
{
fclose (source);
fclose (dest);
exit (5);
}; /* if */
}; /* if */
}
while (a != EOF);
}
/********************************************/
/*ReadInfile: */
/********************************************/
void
ReadInfile (struct ShellyArguments *ShellyArgs, char *fin)
{
char readline[laenge], hilf[laenge], *hp;
FILE *fp;
/* set some defaults */
(*ShellyArgs).output = POV;
(*ShellyArgs).mode = NORMAL;
(*ShellyArgs).Scan = 0.2;
(*ShellyArgs).Threshold = 0.001;
(*ShellyArgs).Scale = 1.0;
(*ShellyArgs).Render = NO;
(*ShellyArgs).N2 = 0;
(*ShellyArgs).N3 = 0;
(*ShellyArgs).N = 0;
mycopystr ("-f +d +w200 +h160", (*ShellyArgs).povargs, '\0');
fp = fopen (fin, "r");
if (fp != NULL)
{
fprintf (stderr, "Parsing:");
while (fgets (readline, laenge, fp) != NULL)
{
fprintf (stderr, ".");
hp = strstr (readline, "alpha:");
if (hp != NULL)
{
mycopystr (hp + 6, hilf, '\0');
(*ShellyArgs).alpha = atof (hilf);
} /* if */
hp = strstr (readline, "beta:");
if (hp != NULL)
{
mycopystr (hp + 5, hilf, '\0');
(*ShellyArgs).beta = atof (hilf);
} /* if */
hp = strstr (readline, "phi:");
if (hp != NULL)
{
mycopystr (hp + 4, hilf, '\0');
(*ShellyArgs).phi = atof (hilf);
} /* if */
hp = strstr (readline, "my:");
if (hp != NULL)
{
mycopystr (hp + 3, hilf, '\0');
(*ShellyArgs).my = atof (hilf);
} /* if */
hp = strstr (readline, "omega:");
if (hp != NULL)
{
mycopystr (hp + 6, hilf, '\0');
(*ShellyArgs).omega = atof (hilf);
} /* if */
hp = strstr (readline, "smin:");
if (hp != NULL)
{
mycopystr (hp + 5, hilf, '\0');
(*ShellyArgs).smin = atof (hilf);
} /* if */
hp = strstr (readline, "smax:");
if (hp != NULL)
{
mycopystr (hp + 5, hilf, '\0');
(*ShellyArgs).smax = atof (hilf);
} /* if */
hp = strstr (readline, "sd:");
if (hp != NULL)
{
mycopystr (hp + 3, hilf, '\0');
(*ShellyArgs).sd = atof (hilf);
} /* if */
hp = strstr (readline, "A:");
if (hp != NULL)
{
mycopystr (hp + 2, hilf, '\0');
(*ShellyArgs).A = atof (hilf);
} /* if */
hp = strstr (readline, "a:");
if (hp != NULL)
{
mycopystr (hp + 2, hilf, '\0');
(*ShellyArgs).a = atof (hilf);
} /* if */
hp = strstr (readline, "b:");
if (hp != NULL)
{
mycopystr (hp + 2, hilf, '\0');
(*ShellyArgs).b = atof (hilf);
} /* if */
hp = strstr (readline, "P:");
if (hp != NULL)
{
mycopystr (hp + 2, hilf, '\0');
(*ShellyArgs).P = atof (hilf);
} /* if */
hp = strstr (readline, "W1:");
if (hp != NULL)
{
mycopystr (hp + 3, hilf, '\0');
(*ShellyArgs).W1 = atof (hilf);
} /* if */
hp = strstr (readline, "W2:");
if (hp != NULL)
{
mycopystr (hp + 3, hilf, '\0');
(*ShellyArgs).W2 = atof (hilf);
} /* if */
hp = strstr (readline, "N:");
if (hp != NULL)
{
mycopystr (hp + 2, hilf, '\0');
(*ShellyArgs).N = atof (hilf);
} /* if */
hp = strstr (readline, "L:");
if (hp != NULL)
{
mycopystr (hp + 2, hilf, '\0');
(*ShellyArgs).L = atof (hilf);
} /* if */
hp = strstr (readline, "omin:");
if (hp != NULL)
{
mycopystr (hp + 5, hilf, '\0');
(*ShellyArgs).omin = atof (hilf);
} /* if */
hp = strstr (readline, "omax:");
if (hp != NULL)
{
mycopystr (hp + 5, hilf, '\0');
(*ShellyArgs).omax = atof (hilf);
} /* if */
hp = strstr (readline, "od:");
if (hp != NULL)
{
mycopystr (hp + 3, hilf, '\0');
(*ShellyArgs).od = atof (hilf);
} /* if */
hp = strstr (readline, "o2d:");
if (hp != NULL)
{
mycopystr (hp + 4, hilf, '\0');
(*ShellyArgs).nod = atof (hilf);
} /* if */
hp = strstr (readline, "Threshold:");
if (hp != NULL)
{
mycopystr (hp + 10, hilf, '\0');
(*ShellyArgs).Threshold = atof (hilf);
} /* if */
hp = strstr (readline, "Scan:");
if (hp != NULL)
{
mycopystr (hp + 5, hilf, '\0');
(*ShellyArgs).Scan = atof (hilf);
} /* if */
hp = strstr (readline, "Scale:");
if (hp != NULL)
{
mycopystr (hp + 6, hilf, '\0');
(*ShellyArgs).Scale = atof (hilf);
} /* if */
hp = strstr (readline, "POV");
if (hp != NULL)
{
(*ShellyArgs).output = POV;
} /* if */
hp = strstr (readline, "RPL");
if (hp != NULL)
{
(*ShellyArgs).output = RPL;
} /* if */
hp = strstr (readline, "T3D");
if (hp != NULL)
{
(*ShellyArgs).output = T3D;
} /* if */
hp = strstr (readline, "RAW");
if (hp != NULL)
{
(*ShellyArgs).output = RAW;
} /* if */
hp = strstr (readline, "NORMAL");
if (hp != NULL)
{
(*ShellyArgs).mode = NORMAL;
} /* if */
hp = strstr (readline, "NODULE");
if (hp != NULL)
{
(*ShellyArgs).mode = NODULE;
} /* if */
hp = strstr (readline, "RENDER");
if (hp != NULL)
{
(*ShellyArgs).Render = YES;
} /* if */
hp = strstr (readline, "POVARGS:");
if (hp != NULL)
mycopystr (hp + 8, (*ShellyArgs).povargs, '\n');
hp = strstr (readline, "P2:");
if (hp != NULL)
{
mycopystr (hp + 3, hilf, '\0');
(*ShellyArgs).P2 = atof (hilf);
} /* if */
hp = strstr (readline, "W12:");
if (hp != NULL)
{
mycopystr (hp + 4, hilf, '\0');
(*ShellyArgs).W12 = atof (hilf);
} /* if */
hp = strstr (readline, "W22:");
if (hp != NULL)
{
mycopystr (hp + 4, hilf, '\0');
(*ShellyArgs).W22 = atof (hilf);
} /* if */
hp = strstr (readline, "N2:");
if (hp != NULL)
{
mycopystr (hp + 3, hilf, '\0');
(*ShellyArgs).N2 = atof (hilf);
} /* if */
hp = strstr (readline, "L2:");
if (hp != NULL)
{
mycopystr (hp + 3, hilf, '\0');
(*ShellyArgs).L2 = atof (hilf);
} /* if */
hp = strstr (readline, "P3:");
if (hp != NULL)
{
mycopystr (hp + 3, hilf, '\0');
(*ShellyArgs).P3 = atof (hilf);
} /* if */
hp = strstr (readline, "W13:");
if (hp != NULL)
{
mycopystr (hp + 4, hilf, '\0');
(*ShellyArgs).W13 = atof (hilf);
} /* if */
hp = strstr (readline, "W23:");
if (hp != NULL)
{
mycopystr (hp + 4, hilf, '\0');
(*ShellyArgs).W23 = atof (hilf);
} /* if */
hp = strstr (readline, "N3:");
if (hp != NULL)
{
mycopystr (hp + 3, hilf, '\0');
(*ShellyArgs).N3 = atof (hilf);
} /* if */
hp = strstr (readline, "L3:");
if (hp != NULL)
{
mycopystr (hp + 3, hilf, '\0');
(*ShellyArgs).L3 = atof (hilf);
} /* if */
hp = strstr (readline, "Off2:");
if (hp != NULL)
{
mycopystr (hp + 5, hilf, '\0');
(*ShellyArgs).Off2 = atof (hilf);
} /* if */
hp = strstr (readline, "Off3:");
if (hp != NULL)
{
mycopystr (hp + 5, hilf, '\0');
(*ShellyArgs).Off3 = atof (hilf);
} /* if */
} /* while */
fprintf (stderr, "\n");
if (fclose (fp) != 0)
fprintf (stderr, "Error while closing file: %s!\n", fin);
}
else
{
fprintf (stderr, "Could not open datafile: %s!\n", fin);
exit (5);
}
} /* ReadInfile */
/********************************************/
/* writepovheader: */
/* */
/********************************************/
void
writepovheader (FILE * fp)
{
fprintf (fp, "/* POV-Scenefile generated by Shelly1.4 */\n");
fprintf (fp, "/* by RANDi: (rschultz@informatik.uni-rostock.de) */\n");
fprintf (fp, "#declare te = pigment { color red 1 green 0 blue 0 }\n");
fprintf (fp, "camera\n{\n location <%.1f,%.1f,%.1f>\n", camx, camy, camz);
fprintf (fp, " look_at <0, 0, 0>\n}\n");
fprintf (fp, "object\n{\n light_source {\n");
fprintf (fp, " <250, 500, 500> color red 1 green 1 blue 1\n }\n");
fprintf (fp, "}\n");
fprintf (fp, "object\n{\n light_source {\n");
fprintf (fp, " <-250, 500, 500> color red 1 green 1 blue 1\n }\n");
fprintf (fp, "}\n");
} /* writepovheader */
/********************************************/
/* writepovtriangles: */
/********************************************/
int
writepovtriangles (FILE * fp, struct punkt *anker1, struct punkt *anker2)
{
struct punkt *p11, *p12, *p21, *p22;
if ((anker1 == NULL) || (anker2 == NULL))
return (0);
p11 = anker1;
p12 = p11;
p21 = anker2;
p22 = p21;
do
{
p11 = p12;
p21 = p22;
p12 = (*p11).next;
p22 = (*p21).next;
if ((p12 != NULL) && (p22 != NULL))
{
fprintf (fp, "triangle{<%.2f,%.2f,%.2f><%.2f,%.2f,%.2f><%.2f,%.2f,%.2f>\n", (*p11).x, (*p11).y, (*p11).z, (*p12).x, (*p12).y, (*p12).z, (*p21).x, (*p21).y, (*p21).z);
fprintf (fp, "pigment{te}}\n");
fprintf (fp, "triangle{<%.2f,%.2f,%.2f><%.2f,%.2f,%.2f><%.2f,%.2f,%.2f>\n", (*p21).x, (*p21).y, (*p21).z, (*p12).x, (*p12).y, (*p12).z, (*p22).x, (*p22).y, (*p22).z);
fprintf (fp, "pigment{te}}\n");
}
}
while ((p12 != NULL) && (p22 != NULL));
return (0);
} /* writepovtriangles */
/********************************************/
/* writepovfinish: */
/********************************************/
void
writepovfinish (FILE * fptemp, FILE * fp)
{
filecopy (fptemp, fp);
}
/********************************************/
/* writerplline: */
/********************************************/
int
writerplline (FILE * fp, struct punkt *anker1)
{
struct punkt *p11, *p12;
if (anker1 == NULL)
return (0);
p11 = anker1;
p12 = p11;
countw++; /* calc number of lines created */
fprintf (fp, "%.3f %.3f %.3f\n", (*p11).x / 100.0, (*p11).y / 100.0, (*p11).z / 100.0);
do
{
p11 = p12;
p12 = (*p11).next;
if (p12 != NULL)
{
fprintf (fp, "%.3f %.3f %.3f\n", (*p12).x / 100.0, (*p12).y / 100.0, (*p12).z / 100.0);
}
}
while (p12 != NULL);
return (0);
} /* writerplline */
/********************************************/
/* writerplfinish: */
/* */
/********************************************/
void
writerplfinish (FILE * fptemp, FILE * fp)
{
filecopy (fptemp, fp);
fprintf (fp, "%d\n", counth); /* height width of the mesh */
fprintf (fp, "%d\n", countw);
fprintf (fp, "3\n0\n255 255 255 0\n"); /* RGBA */
fprintf (fp, "\"Shell\"\n0\n"); /* Name */
fprintf (fp, "\"CEND\"\n");
fprintf (fp, "C_MESH DROP\n");
} /* writerplfinish */
/********************************************/
/* writet3dheader: */
/* */
/********************************************/
void
writet3dheader (FILE * fp)
{
char percent = '%';
fprintf (fp, " %c T3Dlib-data-file generated by Shelly1.4\n", percent);
fprintf (fp, " %c the ShellShapeGenerator by RANDi : \n", percent);
fprintf (fp, " %c (rschultz@informatik.uni-rostock.de)\n", percent);
fprintf (fp, "OBJ Begin \"Hierarchy 1\"\n");
fprintf (fp, " DESC Begin \"Object 1 at level 1 of hierarchy 1\"\n");
fprintf (fp, " NAME \"SHELL\"\n");
fprintf (fp, " SHAP Shape = 2\n");
fprintf (fp, " SHAP Lamp = 0\n");
fprintf (fp, " POSI X=0 Y=0 Z=0\n");
fprintf (fp, " AXIS XAxis X=1 Y=0 Z=0\n");
fprintf (fp, " AXIS YAxis X=0 Y=1 Z=0\n");
fprintf (fp, " AXIS ZAxis X=0 Y=0 Z=1\n");
fprintf (fp, " SIZE X=32 Y=32 Z=32\n");
} /* writet3dheader */
/********************************************/
/* writet3dline: */
/********************************************/
int
writet3dline (FILE * fp, struct punkt *anker1)
{
struct punkt *p11, *p12;
static int called = 0, count = 0;
if (anker1 == NULL)
return (0);
if (called == 0)
{
called = 1;
count = -1;
countw = 0;
}
countw++;
p11 = anker1;
p12 = p11;
fprintf (fp, " PNTS Point[%d] X=%.3f Y=%.3f Z=%.3f\n", ++count, (*p11).x, (*p11).y, (*p11).z);
do
{
p11 = p12;
p12 = (*p11).next;
if (p12 != NULL)
{
fprintf (fp, " PNTS Point[%d] X=%.3f Y=%.3f Z=%.3f\n", ++count, (*p12).x, (*p12).y, (*p12).z);
}
}
while (p12 != NULL);
return (0);
} /* writet3dline */
/********************************************/
/* writet3dfinish: */
/* */
/********************************************/
void
writet3dfinish (FILE * fptemp, FILE * fp)
{
int edges = 0, faces = 0, edgecount = 0, facecount = 0, a = 0, b = 0,
r = 0, r2 = 0, r3 = 0;
int point1 = 0, point2 = 0, edge1 = 0, edge2 = 0, edge3 = 0;
fprintf (stderr, "\nWriting additional T3Dlib-Data ...");
fprintf (fp, " PNTS PCount %d\n", countp);
filecopy (fptemp, fp);
edges = (counth * (countw - 1) + countw * (counth - 1) + (counth - 1) * (countw - 1));
/* number of edges! */
fprintf (fp, " EDGE ECount %d\n", edges);
/* write horizontal edges */
for (a = 0; a < counth; a++)
{
r = a;
for (b = 0; b < (countw - 1); b++)
{
point1 = r;
point2 = r + counth;
fprintf (fp, " EDGE Edge[%d] %d %d\n", edgecount++, point1, point2);
r = r + counth;
}
}
/* write vertical edges */
for (a = 0; a < countw; a++)
{
r = a * counth;
for (b = 0; b < (counth - 1); b++)
{
point1 = r + b;
point2 = r + b + 1;
fprintf (fp, " EDGE Edge[%d] %d %d\n", edgecount++, point1, point2);
}
}
/* write diagonal edges */
for (a = 0; a < counth - 1; a++)
{
r = a;
for (b = 0; b < (countw - 1); b++)
{
point1 = r;
point2 = r + counth + 1;
fprintf (fp, " EDGE Edge[%d] %d %d\n", edgecount++, point1, point2);
r = r + counth;
}
}
/* ohhh boy, THIS (^^^) took me time ! :), now to that faces! */
/* write faces */
faces = 2 * (countw - 1) * (counth - 1);
fprintf (fp, " FACE TCount %d\n", faces);
r = 0;
r3 = countw * (counth - 1) + counth * (countw - 1);
for (a = 0; a < counth - 1; a++)
{
r2 = counth * (countw - 1) + a;
for (b = 0; b < countw - 1; b++)
{
edge1 = r + countw - 1;
edge2 = r2;
edge3 = r3;
fprintf (fp, " FACE Connect[%d] %d %d %d\n", facecount++, edge1, edge2, edge3);
edge1 = r;
edge2 = r2 + counth - 1;
edge3 = r3;
fprintf (fp, " FACE Connect[%d] %d %d %d\n", facecount++, edge1, edge2, edge3);
r++;
r2 = r2 + counth - 1;
r3++;
}
}
fprintf (fp, " COLR R=98 G=68 B=58\n");
fprintf (fp, " REFL R=0 G=0 B=0\n");
fprintf (fp, " TRAN R=0 G=0 B=0\n");
fprintf (fp, " SPC1 R=0 G=0 B=0\n");
fprintf (fp, " End DESC \"Object 1 at level 1 of hierarchy 1\"\n");
fprintf (fp, " TOBJ \"Object 0 at level 1 of hierarchy 1\"\n");
fprintf (fp, "End OBJ \"Hierarchy 1\"\n");
} /* writet3dfinish */
/********************************************/
/* writerawtriangles: */
/********************************************/
int
writerawtriangles (FILE * fp, struct punkt *anker1, struct punkt *anker2)
{
struct punkt *p11, *p12, *p21, *p22;
if ((anker1 == NULL) || (anker2 == NULL))
return (0);
p11 = anker1;
p12 = p11;
p21 = anker2;
p22 = p21;
do
{
p11 = p12;
p21 = p22;
p12 = (*p11).next;
p22 = (*p21).next;
if ((p12 != NULL) && (p22 != NULL))
{
fprintf (fp, "%.2f %.2f %.2f %.2f %.2f %.2f %.2f %.2f %.2f\n", (*p11).x, (*p11).y, (*p11).z, (*p12).x, (*p12).y, (*p12).z, (*p21).x, (*p21).y, (*p21).z);
fprintf (fp, "%.2f %.2f %.2f %.2f %.2f %.2f %.2f %.2f %.2f\n", (*p21).x, (*p21).y, (*p21).z, (*p12).x, (*p12).y, (*p12).z, (*p22).x, (*p22).y, (*p22).z);
}
}
while ((p12 != NULL) && (p22 != NULL));
return (0);
} /* writerawtriangles */
/********************************************/
/*calcg: */
/********************************************/
double
calcg (double O, double N)
{
if (N == 0)
return (0);
else
return ((2 * pi) / N * (O * N / (2 * pi) - round (O * N / (2 * pi))));
} /* calcg */
/********************************************/
/*calck: */
/********************************************/
double
calck (struct ShellyArguments *ShellyArgs, double S, double O)
{
static double N, N2, N3, L, L2, L3, W1, W2, W12, W13, W22, W23, P, P2,
P3, Off2, Off3;
double k = 0, g;
static int called = 0;
if (called == 0)
{
N = (*ShellyArgs).N;
W1 = (*ShellyArgs).W1 * pi / 180;
W2 = (*ShellyArgs).W2 * pi / 180;
P = (*ShellyArgs).P * pi / 180;
L = (*ShellyArgs).L;
N2 = (*ShellyArgs).N2;
W12 = (*ShellyArgs).W12 * pi / 180;
W22 = (*ShellyArgs).W22 * pi / 180;
P2 = (*ShellyArgs).P2 * pi / 180;
L2 = (*ShellyArgs).L2;
N3 = (*ShellyArgs).N3;
W13 = (*ShellyArgs).W13 * pi / 180;
W23 = (*ShellyArgs).W23 * pi / 180;
P3 = (*ShellyArgs).P3 * pi / 180;
L3 = (*ShellyArgs).L3;
Off2 = (*ShellyArgs).Off2 * pi / 180;
Off3 = (*ShellyArgs).Off3 * pi / 180;
}
g = calcg (O, N);
if (N != 0)
k = L * exp (-(2 * (S - P) / W1) * (2 * (S - P) / W1)) * exp (-(2 * g / W2) * (2 * g / W2));
g = calcg (O + Off2, N2);
if (N2 != 0)
k = k + (L2 * exp (-(2 * (S - P2) / W12) * (2 * (S - P2) / W12)) * exp (-(2 * g / W22) * (2 * g / W22)));
g = calcg (O + Off3, N3);
if (N3 != 0)
k = k + (L3 * exp (-(2 * (S - P3) / W13) * (2 * (S - P3) / W13)) * exp (-(2 * g / W23) * (2 * g / W23)));
called = 1;
return (k);
} /* calck */
/********************************************/
/*innodule: */
/********************************************/
double
innodule (struct ShellyArguments *ShellyArgs, double sc, double O)
{
static double N, N2, N3, L, L2, L3, W2, W22, W23, Off2, Off3;
double k1 = 0, k2 = 0, g;
static int called = 0;
if (called == 0)
{
N = (*ShellyArgs).N;
W2 = (*ShellyArgs).W2 * pi / 180;
L = (*ShellyArgs).L;
N2 = (*ShellyArgs).N2;
W22 = (*ShellyArgs).W22 * pi / 180;
L2 = (*ShellyArgs).L2;
N3 = (*ShellyArgs).N3;
W23 = (*ShellyArgs).W23 * pi / 180;
L3 = (*ShellyArgs).L3;
Off2 = (*ShellyArgs).Off2 * pi / 180;
Off3 = (*ShellyArgs).Off3 * pi / 180;
called = 1;
}
g = calcg (O, N);
if (N != 0)
k1 = L * exp (-(2 * g / W2) * (2 * g / W2));
g = calcg (O + Off2, N2);
if (N2 != 0)
k1 = k1 + (L2 * exp (-(2 * g / W22) * (2 * g / W22)));
g = calcg (O + Off3, N3);
if (N3 != 0)
k1 = k1 + (L3 * exp (-(2 * g / W23) * (2 * g / W23)));
g = calcg (O + sc, N);
if (N != 0)
k2 = L * exp (-(2 * g / W2) * (2 * g / W2));
g = calcg (O + Off2 + sc, N2);
if (N2 != 0)
k2 = k2 + (L2 * exp (-(2 * g / W22) * (2 * g / W22)));
g = calcg (O + Off3 + sc, N3);
if (N3 != 0)
k2 = k2 + (L3 * exp (-(2 * g / W23) * (2 * g / W23)));
return (fabs (k1) - fabs (k2));
} /* innodule */
/********************************************/
/*calccamera: */
/********************************************/
void
calccamera (double x, double y, double z)
{
static double biggest;
if ((fabs (x) > fabs (y)) && (fabs (x) > fabs (z)))
if (fabs (x) > biggest)
{
biggest = fabs (x);
camy = biggest * 1.5;
camz = biggest * 1.5;
}
if ((fabs (y) > fabs (x)) && (fabs (y) > fabs (z)))
if (fabs (y) > biggest)
{
biggest = fabs (y);
camy = biggest * 1.5;
camz = biggest * 1.5;
}
if ((fabs (z) > fabs (y)) && (fabs (z) > fabs (x)))
if (fabs (z) > biggest)
{
biggest = fabs (z);
camy = biggest * 1.5;
camz = biggest * 1.5;
}
} /* calccamera */
/**********************************************/
/* CalcLine: */
/* */
/**********************************************/
int
calcline (double O, struct ShellyArguments *ShellyArgs, struct punkt **list)
{
struct punkt *list1 = NULL, *L1p1, *L1p2;
double x, y, z, R, S, Re, k;
static double my;
static double smin, smax, sd, a, b, A, beta, phi, omega, alpha, Scale;
static int called = 0;
if (called == 0)
{
smin = (*ShellyArgs).smin * pi / 180;
smax = (*ShellyArgs).smax * pi / 180;
sd = (*ShellyArgs).sd * pi / 180;
alpha = (*ShellyArgs).alpha * pi / 180;
beta = (*ShellyArgs).beta * pi / 180;
phi = (*ShellyArgs).phi * pi / 180;
omega = (*ShellyArgs).omega * pi / 180;
my = (*ShellyArgs).my * pi / 180;
a = (*ShellyArgs).a;
b = (*ShellyArgs).b;
A = (*ShellyArgs).A;
Scale = (*ShellyArgs).Scale;
called = 1;
}
counth = 0;
for (S = smin; (S + sd) < smax; S = S + sd)
{
counth++;
countp++;
Re = pow ((pow (a, -2.0) * (cos (S) * cos (S)) + pow (b, -2.0) * (sin (S) * sin (S))), -0.5);
k = calck (ShellyArgs, S, O);
R = Re + k;
/* alternatively: */
/* R = pow((pow(a,2.0)*pow(cos(S),2.0)+pow(b,2.0)*pow(sin(S),2.0)),0.5); */
x = Scale * (A * sin (beta) * cos (O) + R * cos (S + phi) * cos (O + omega) - R * sin (my) * sin (S + phi) * sin (O)) * exp (O * cot (alpha));
y = Scale * (-1 * A * sin (beta) * sin (O) - R * cos (S + phi) * sin (O + omega) - R * sin (my) * sin (S + phi) * cos (O)) * exp (O * cot (alpha));
z = Scale * (-1 * A * cos (beta) + R * sin (S + phi) * cos (my)) * exp (O * cot (alpha));
calccamera (x, y, z);
if ((L1p1 = calloc (1, sizeof (struct punkt))) == NULL)
{
fprintf (stderr, "Shelly: NOT ENOUGH MEMORY!!! ... exiting ... !\n");
if (S != smin)
myfree (list1);
return (5);
} /* if */
if (S == smin)
list1 = L1p1;
else
(*L1p2).next = L1p1;
L1p2 = L1p1;
(*L1p1).x = x;
(*L1p1).y = y;
(*L1p1).z = z;
} /* for */
*list = list1;
return (0);
} /* calcline */
/**********************************************/
/* CalcNodule: */
/* SSIA :) */
/**********************************************/
void
CalcNodule (struct ShellyArguments *ShellyArgs, char *fout)
{
struct punkt *list1 = NULL, *list2;
double sc, t, O, Oold, omin, omax, od, nod;
FILE *fptemp, *fp;
char *hilf, temp[laenge];
omin = (*ShellyArgs).omin * pi / 180;
omax = (*ShellyArgs).omax * pi / 180;
od = (*ShellyArgs).od * pi / 180;
nod = (*ShellyArgs).nod * pi / 180;
O = omin;
t = (*ShellyArgs).Threshold;
sc = (*ShellyArgs).Scan;
mycopystr (fout, temp, '\0');
hilf = strchr (temp, '\0');
if (hilf != NULL)
mycopystr (".tmp", hilf, '\0');
if ((fptemp = fopen (temp, "w+")) == NULL)
{
fprintf (stderr, "Could not open outfile: %s!\n", temp);
exit (5);
}
if ((fp = fopen (fout, "w")) == NULL)
{
fprintf (stderr, "Could not open outfile: %s!\n", fout);
exit (5);
}
fprintf (stderr, "Calculating the Shell:");
if (calcline (omin, ShellyArgs, &list1) != 0)
exit (5);
if ((*ShellyArgs).output == RPL)
writerplline (fptemp, list1);
if ((*ShellyArgs).output == T3D)
writet3dline (fptemp, list1);
while (O <= omax)
{
Oold = O;
while ((innodule (ShellyArgs, sc, O) <= t) && (O - Oold < od))
O = O + sc;
if (calcline (O, ShellyArgs, &list2) != 0)
exit (5);
fprintf (stderr, ".");
fflush (stderr);
if ((*ShellyArgs).output == RPL)
writerplline (fptemp, list1);
if ((*ShellyArgs).output == POV)
writepovtriangles (fptemp, list1, list2);
if ((*ShellyArgs).output == T3D)
writet3dline (fptemp, list1);
if ((*ShellyArgs).output == RAW)
writerawtriangles (fp, list1, list2);
myfree (list1);
list1 = list2;
if (innodule (ShellyArgs, sc, O) > t)
{
while ((O <= omax) && (innodule (ShellyArgs, sc, O) > t / 2))
{
O = O + nod;
if (calcline (O, ShellyArgs, &list2) != 0)
exit (5);
if ((*ShellyArgs).output == RPL)
writerplline (fptemp, list1);
if ((*ShellyArgs).output == POV)
writepovtriangles (fptemp, list1, list2);
if ((*ShellyArgs).output == T3D)
writet3dline (fptemp, list1);
if ((*ShellyArgs).output == RAW)
writerawtriangles (fp, list1, list2);
fprintf (stderr, ".");
fflush (stderr);
myfree (list1);
list1 = list2;
} /* while */
} /* if */
} /* while */
if ((*ShellyArgs).output == POV)
writepovheader (fp);
if ((*ShellyArgs).output == T3D)
writet3dheader (fp);
if ((*ShellyArgs).output == RPL)
writerplfinish (fptemp, fp);
if ((*ShellyArgs).output == T3D)
writet3dfinish (fptemp, fp);
if ((*ShellyArgs).output == POV)
writepovfinish (fptemp, fp);
fprintf (stderr, "\n");
myfree (list1);
if (fclose (fptemp) != 0)
fprintf (stderr, "Error while closing file: %s!\n", temp);
if (fclose (fp) != 0)
fprintf (stderr, "Error while closing file: %s!\n", fout);
unlink (temp);
} /* CalcNodule */
/**********************************************/
/* CalcShell: */
/* SSIA :) */
/**********************************************/
void
CalcShell (struct ShellyArguments *ShellyArgs, char *fout)
{
struct punkt *list1 = NULL, *list2;
double O, omin, omax, od;
FILE *fptemp, *fp;
char temp[laenge], *hilf;
omin = (*ShellyArgs).omin * pi / 180;
omax = (*ShellyArgs).omax * pi / 180;
od = (*ShellyArgs).od * pi / 180;
mycopystr (fout, temp, '\0');
hilf = strchr (temp, '\0');
if (hilf != NULL)
mycopystr (".tmp", hilf, '\0');
if ((fptemp = fopen (temp, "w+")) == NULL)
{
fprintf (stderr, "Could not open outfile: %s!\n", temp);
exit (5);
}
if ((fp = fopen (fout, "w")) == NULL)
{
fprintf (stderr, "Could not open outfile: %s!\n", fout);
exit (5);
}
fprintf (stderr, "Calculating the Shell:");
if (calcline (omin, ShellyArgs, &list1) != 0)
exit (5);
if ((*ShellyArgs).output == RPL)
writerplline (fptemp, list1);
if ((*ShellyArgs).output == T3D)
writet3dline (fptemp, list1);
for (O = omin + od; (O + od) < omax; O = O + od)
{
counth = 0;
if (calcline (O, ShellyArgs, &list2) != 0)
exit (5);
fprintf (stderr, ".");
fflush (stderr);
if ((*ShellyArgs).output == RPL)
writerplline (fptemp, list1);
if ((*ShellyArgs).output == POV)
writepovtriangles (fptemp, list1, list2);
if ((*ShellyArgs).output == T3D)
writet3dline (fptemp, list1);
if ((*ShellyArgs).output == RAW)
writerawtriangles (fp, list1, list2);
myfree (list1);
list1 = list2;
} /* for */
if ((*ShellyArgs).output == POV)
writepovheader (fp);
if ((*ShellyArgs).output == T3D)
writet3dheader (fp);
if ((*ShellyArgs).output == RPL)
writerplfinish (fptemp, fp);
if ((*ShellyArgs).output == T3D)
writet3dfinish (fptemp, fp);
if ((*ShellyArgs).output == POV)
writepovfinish (fptemp, fp);
fprintf (stderr, "\n");
myfree (list1);
if (fclose (fptemp) != 0)
fprintf (stderr, "Error while closing file: %s!\n", temp);
if (fclose (fp) != 0)
fprintf (stderr, "Error while closing file: %s!\n", fout);
unlink (temp);
} /* CalcShell */
/**********************************************/
/* RenderPov: */
/* invoke pov for rendering */
/**********************************************/
void
RenderPov (struct ShellyArguments *ShellyArgs, char *fout)
{
char call[laenge];
printf ("Rendering...\n");
mycopystr ("pov ", call, '\0');
mycopystr ((*ShellyArgs).povargs, &call[4], '\0');
strcat (call, " +i");
strcat (call, fout);
system (call);
} /* RenderPov */
/********************************************/
/*main: */
/********************************************/
int
main (int ac, char **av)
{
struct ShellyArguments ShellyArgs;
fprintf (stderr, "ShellyV1.4, the ShellShapeGenerator by RANDi\n");
if (ac != 3)
{
fprintf (stderr, "USAGE:\n\n");
fprintf (stderr, " 'shelly infilename outfilename'\n\n");
exit (1);
} /* if */
ReadInfile (&ShellyArgs, av[1]);
if (ShellyArgs.mode == NORMAL)
CalcShell (&ShellyArgs, av[2]);
if (ShellyArgs.mode == NODULE)
CalcNodule (&ShellyArgs, av[2]);
if (ShellyArgs.Render == YES)
if (ShellyArgs.output != POV)
fprintf (stderr, "Rendering is only available for POV-output!\n(Ever tried to feed a RPL-Macro into POV? ;))\n");
else
RenderPov (&ShellyArgs, av[2]);
exit (0);
}